# Copyright (C) 2018 Tom Li <tomli at tomli.me>.
#
# To the extent possible under law, I, Tom Li, has waived all copyright
# and related or neighboring rights to this work. You may copy, modify,
# distribute and perform the work, for all purposes.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
# THE SOFTWARE.

import sys
from pprint import pprint

def parse(dat):
    struct = []

    state = "STATE_INITIAL"
    ptr = [struct]

    key_buf = []
    val_buf = []
    last_type = ""

    dat = dat.replace("return {", "{")

    for i in dat:
        if i.isspace() and (not "STR" in state):
            continue

        previous_state = state

        if i == "{":
            state = "STATE_BEGIN_DICT"
        elif i == "}":
            state = "STATE_END_DICT"
        elif i == "[":
            state = "STATE_BEGIN_KEY"
        elif i == "]":
            state = "STATE_END_KEY"
        elif i == "\"":
            if state not in ["STATE_BEGIN_STR", "STATE_STR"]:
                state = "STATE_BEGIN_STR"
            elif state in ["STATE_BEGIN_STR", "STATE_STR"]:
                state = "STATE_END_STR"
        elif i == "=":
            if state not in ["STATE_BEGIN_STR", "STATE_STR"]:
                state = "STATE_ASSIGNMENT"
        elif i == ";":
            if previous_state == "STATE_VAL":
                state = "STATE_END_VAL"
            state = "STATE_END_ENTRY"
        else:
            if state == "STATE_BEGIN_KEY":
                state = "STATE_VAL"
            elif state == "STATE_BEGIN_STR":
                state = "STATE_STR"
            elif state == "STATE_ASSIGNMENT":
                state = "STATE_VAL"
        if previous_state == "STATE_BEGIN_STR":
            state = "STATE_STR"

        #print("char: %s \t state: %s" % (i, state))
        #print("previous ptr: ", end="")
        #pprint(ptr)

        if state == "STATE_BEGIN_DICT":
            dic = {}
            if ptr[-1] == None:
                #print(last_type)
                if last_type == "key":
                    ptr[-2][key_buf[0]] = dic
                elif last_type == "val":
                    ptr[-2][val_buf] = dic
                else:
                    assert(False)
                ptr.pop()
            else:
                ptr[-1].append(dic)
            ptr.append(dic)
        if state == "STATE_BEGIN_KEY":
            last_type = "key"
            key_buf.clear()
            ptr.append(key_buf)
        if state == "STATE_BEGIN_STR":
            if previous_state != "STATE_BEGIN_KEY":
                last_type = "val"
                val_buf.clear()
                ptr.append(val_buf)
        if state in ["STATE_VAL", "STATE_STR"]:
            if previous_state == "STATE_ASSIGNMENT":
                ptr.append(val_buf)
            ptr[-1] += i
        if state in ["STATE_END_DICT"]:
            ptr.pop()
        if state in ["STATE_END_KEY", "STATE_END_ENTRY"]:
            if previous_state == "STATE_END_DICT":
                continue
            if previous_state == "STATE_VAL":
                if ("".join(ptr[-1])) == "false":
                    ptr[-1].clear()
                    ptr[-1].append(False)
                elif ("".join(ptr[-1])) == "true":
                    ptr[-1].clear()
                    ptr[-1].append(True)
                else:
                    val = eval("".join(ptr[-1]))
                    ptr[-1].clear()
                    ptr[-1].append(val)
            else:
                assert(previous_state in ["STATE_END_STR"])
                string = "".join(ptr[-1])
                ptr[-1].clear()
                ptr[-1].append(string)
            if isinstance(ptr[-2], dict):
                ptr[-2][ptr[-1][0]] = None
            elif isinstance(ptr[-2], type(None)):
                #print("key 0 is", tuple(ptr[-3].keys())[0])
                #print("key_buf is", key_buf)
                #print("val_buf is", val_buf)
                ptr[-3]["".join(key_buf)] = ptr[-1][0]
                ptr.pop()
                ptr.pop()
            else:
                assert(False)
            val_buf.clear()
        if state == "STATE_ASSIGNMENT":
            ptr[-1] = ptr[-2][ptr[-1][0]]

        #print("struct: ", end="")
        #pprint(struct)
        #print("new ptr: ", end="")
        #pprint(ptr)
        #print()

    assert(len(struct) == 1)
    return struct[0]

for arg in sys.argv[1:]:
    score = 0

    f = open(arg, "r")
    dat = f.read()
    f.close()

    try:
        roster = parse(dat)
    except AssertionError as e:
        print("============ INTERNAL ERROR ============", file=sys.stderr)
        print("The program fails to parse \"%s\", please" % arg, file=sys.stderr)
        print("submit a bug report, with your file attached.", file=sys.stderr)
        print("============ INTERNAL ERROR ============", file=sys.stderr)
        raise e

    server = []
    none_subscription = 0
    for s in tuple(roster.keys()):
        if not isinstance(s, str):
            continue
        if "@" not in s:
            continue
        server.append(s.split("@")[1])
        if roster[s]["subscription"] == "none":
            none_subscription += 1

    if len(server) >= 50:
        score += 1

    if len(set(server)) >= 20:
        score += 1

    if "pending" in roster and len(roster["pending"]) > 20:
        score += 1

    if len(server) > 0 and (none_subscription / len(server)) >= 0.55:
        score += 2

    if score >= 3:
        print(arg, score)
